package clipboard

import (
	"fmt"
	"regexp"
	"strings"

	"golang.org/x/net/html"
)

// ExcelClipboardParser Excel剪贴板解析器
type ExcelClipboardParser struct {
	lastParsedHTML string
}

// ParseResult 解析结果
type ParseResult struct {
	Success     bool
	Data        [][]string
	HTML        string
	Error       string
	RowCount    int
	ColumnCount int
}

// NewExcelClipboardParser 创建新的Excel剪贴板解析器
func NewExcelClipboardParser() *ExcelClipboardParser {
	return &ExcelClipboardParser{}
}

// ParseExcelHTML 解析Excel HTML内容
func (p *ExcelClipboardParser) ParseExcelHTML(htmlContent string) *ParseResult {
	// 检查是否是Excel格式
	if !p.isExcelHTML(htmlContent) {
		return &ParseResult{
			Success: false,
			Error:   "剪贴板内容不是Excel格式的HTML",
		}
	}

	// 保存最后解析的HTML
	p.lastParsedHTML = htmlContent

	// 解析HTML为二维数组
	data, err := p.parseHTMLToArray(htmlContent)
	if err != nil {
		return &ParseResult{
			Success: false,
			Error:   fmt.Sprintf("解析Excel HTML失败: %v", err),
		}
	}

	return &ParseResult{
		Success:     true,
		Data:        data,
		HTML:        htmlContent,
		RowCount:    len(data),
		ColumnCount: len(data[0]),
	}
}

// isExcelHTML 检查HTML是否来自Excel
func (p *ExcelClipboardParser) isExcelHTML(html string) bool {
	// Excel特征标记
	excelMarkers := []string{
		"mso-",
		"excel",
		"spreadsheet",
		"urn:schemas-microsoft-com:office:excel",
		"xmlns:x=\"urn:schemas-microsoft-com:office:excel\"",
	}

	// 检查表格结构
	hasTableStructure := regexp.MustCompile(`<table[^>]*>`).MatchString(html) &&
		regexp.MustCompile(`<tr[^>]*>`).MatchString(html) &&
		(regexp.MustCompile(`<td[^>]*>`).MatchString(html) || regexp.MustCompile(`<th[^>]*>`).MatchString(html))

	if !hasTableStructure {
		return false
	}

	// 检查是否至少包含一个Excel特征标记
	for _, marker := range excelMarkers {
		if strings.Contains(strings.ToLower(html), strings.ToLower(marker)) {
			return true
		}
	}

	return false
}

// parseHTMLToArray 将HTML解析为二维数组
func (p *ExcelClipboardParser) parseHTMLToArray(htmlContent string) ([][]string, error) {
	// 解析HTML
	doc, err := html.Parse(strings.NewReader(htmlContent))
	if err != nil {
		return nil, fmt.Errorf("解析HTML失败: %v", err)
	}

	// 查找表格元素
	var table *html.Node
	var findTable func(*html.Node)
	findTable = func(n *html.Node) {
		if n.Type == html.ElementNode && n.Data == "table" {
			table = n
			return
		}
		for c := n.FirstChild; c != nil; c = c.NextSibling {
			findTable(c)
		}
	}
	findTable(doc)

	if table == nil {
		return nil, fmt.Errorf("HTML中未找到表格元素")
	}

	// 解析表格数据
	var result [][]string
	var currentRow []string

	var traverse func(*html.Node)
	traverse = func(n *html.Node) {
		switch n.Type {
		case html.ElementNode:
			switch n.Data {
			case "tr":
				// 开始新行
				if len(currentRow) > 0 {
					result = append(result, currentRow)
					currentRow = []string{}
				}
			case "td", "th":
				// 处理单元格
				cellText := p.extractCellText(n)
				colspan := p.getAttribute(n, "colspan")
				rowspan := p.getAttribute(n, "rowspan")

				// 添加单元格文本
				currentRow = append(currentRow, cellText)

				// 处理列跨度
				if colspan > 1 {
					for i := 1; i < colspan; i++ {
						currentRow = append(currentRow, "")
					}
				}

				// 注意：简单实现中不处理行跨度的复杂情况
				_ = rowspan
			}
		case html.TextNode:
			// 文本节点在上面的单元格处理中已经处理
		}

		// 递归遍历子节点
		for c := n.FirstChild; c != nil; c = c.NextSibling {
			traverse(c)
		}
	}

	traverse(table)

	// 添加最后一行
	if len(currentRow) > 0 {
		result = append(result, currentRow)
	}

	return result, nil
}

// extractCellText 提取单元格文本
func (p *ExcelClipboardParser) extractCellText(node *html.Node) string {
	var text strings.Builder

	var extractText func(*html.Node)
	extractText = func(n *html.Node) {
		switch n.Type {
		case html.TextNode:
			text.WriteString(n.Data)
		case html.ElementNode:
			// 处理HTML换行标签
			if n.Data == "br" {
				text.WriteString("\n")
			}
			// 递归处理子节点
			for c := n.FirstChild; c != nil; c = c.NextSibling {
				extractText(c)
			}
		}
	}

	extractText(node)
	result := text.String()

	// 只去除首尾空白字符，但保留换行符
	trimmed := strings.TrimLeft(result, " \t")
	trimmed = strings.TrimRight(trimmed, " \t")

	return trimmed
}

// getAttribute 获取属性值
func (p *ExcelClipboardParser) getAttribute(node *html.Node, name string) int {
	for _, attr := range node.Attr {
		if attr.Key == name {
			var value int
			_, err := fmt.Sscanf(attr.Val, "%d", &value)
			if err == nil {
				return value
			}
		}
	}
	return 1
}

// GetLastParsedHTML 获取最后解析的HTML
func (p *ExcelClipboardParser) GetLastParsedHTML() string {
	return p.lastParsedHTML
}

// FormatAsCSV 格式化为CSV
func FormatAsCSV(data [][]string) string {
	var result strings.Builder

	for i, row := range data {
		for j, cell := range row {
			if j > 0 {
				result.WriteString(",")
			}

			// 如果包含逗号、引号或换行符，用引号括起来
			if strings.Contains(cell, ",") || strings.Contains(cell, "\"") || strings.Contains(cell, "\n") {
				// 转义引号
				escaped := strings.ReplaceAll(cell, "\"", "\"\"")
				result.WriteString("\"")
				result.WriteString(escaped)
				result.WriteString("\"")
			} else {
				result.WriteString(cell)
			}
		}
		if i < len(data)-1 {
			result.WriteString("\n")
		}
	}

	return result.String()
}

// FormatAsHTMLTable 格式化为HTML表格
func FormatAsHTMLTable(data [][]string, useFirstRowAsHeader bool) string {
	if len(data) == 0 {
		return "<table></table>"
	}

	var result strings.Builder
	result.WriteString("<table border=\"1\" cellpadding=\"5\" cellspacing=\"0\">")

	for i, row := range data {
		result.WriteString("<tr>")

		for _, cell := range row {
			var tag string
			if useFirstRowAsHeader && i == 0 {
				tag = "th"
			} else {
				tag = "td"
			}
			result.WriteString("<")
			result.WriteString(tag)
			result.WriteString(">")
			result.WriteString(html.EscapeString(cell))
			result.WriteString("</")
			result.WriteString(tag)
			result.WriteString(">")
		}

		result.WriteString("</tr>")
	}

	result.WriteString("</table>")
	return result.String()
}

// ClearLastParsedHTML 清除最后解析的HTML
func (p *ExcelClipboardParser) ClearLastParsedHTML() {
	p.lastParsedHTML = ""
}
